package com.titaniume.java2;

import org.junit.Test;

import java.io.PrintStream;
import java.util.Comparator;
import java.util.function.BiPredicate;
import java.util.function.Consumer;
import java.util.function.Function;
import java.util.function.Supplier;

/**
 * 方法引用的使用
 *
 *
 *  格式： 类（对象） :: 方法名
 *  具体分为如下三种情况
 *   对象:: 非静态方法
 *   类:: 静态方法
 *   类::非静态方法
 *
 *   要求： 接口中的抽象方的形参列表和返回值类型与方法引用的方法
 *   的形参列表与返回值类型相同！
 *
 * Created by shkstart.
 */
public class MethodRefTest {

	// 情况一：对象 :: 实例方法
	//Consumer中的void accept(T t)
	//PrintStream中的void println(T t)
	@Test
	public void test1() {

		Consumer<String> consumer1 = str -> System.out.println(str);
		consumer1.accept("hello");

		System.out.println("********************************");

		PrintStream printStream = System.out;
		Consumer<String> consumer2 = printStream::println;
		consumer2.accept("world");

	}
	
	//Supplier中的T get()
	//Employee中的String getName()
	@Test
	public void test2() {

		Employee employee = new Employee(1001, "jack", 23, 3434);
		Supplier<String> supplier = () -> employee.getName();
		System.out.println(supplier.get());

		System.out.println("********************************");

		Supplier<String> supplier2 =  employee::getName;
		System.out.println(supplier2.get());



	}

	// 情况二：类 :: 静态方法
	//Comparator中的int compare(T t1,T t2)
	//Integer中的int compare(T t1,T t2)
	@Test
	public void test3() {
		Comparator<Integer> comparator1 = (t1,t2) ->Integer.compare(t1,t2);
		System.out.println(comparator1.compare(12, 23));
		System.out.println("********************************");

		Comparator<Integer> comparator2 = Integer::compareTo;
		System.out.println(comparator2.compare(12, 23));

	}
	
	//Function中的R apply(T t)
	//Math中的Long round(Double d)
	@Test
	public void test4() {

		Function<Double, Long> function0 = new Function<Double, Long>() {
			@Override
			public Long apply(Double aDouble) {
				return Math.round(aDouble);
			}
		};
		System.out.println(function0.apply(123.0));

		System.out.println("********************************");


		Function<Double,Long> function1 = (d) -> Math.round(d);
		System.out.println(function0.apply(123.0));

		System.out.println("********************************");

		Function<Double,Long> function2 = Math::round;

		System.out.println(function2.apply(123.0));



	}

	// 情况三：类 :: 实例方法 (有难度)
	// Comparator中的int comapre(T t1,T t2)
	// String中的int t1.compareTo(t2)
	@Test
	public void test5() {

		Comparator<String> comparator1 = (t1,t2) -> t1.compareTo(t2);
		System.out.println(comparator1.compare("abc","abd"));

		System.out.println("********************************");



		Comparator<String> comparator2 = String::compareTo;
		System.out.println(comparator2.compare("abc","abd"));



	}

	//BiPredicate中的boolean test(T t1, T t2);
	//String中的boolean t1.equals(t2)
	@Test
	public void test6() {

		BiPredicate<String,String> predicate1 = (t1,t2) -> t1.equals(t2);
		System.out.println(predicate1.test("abc", "abc"));

		System.out.println("********************************");



		BiPredicate<String,String> predicate2 = String::equals;
		System.out.println(predicate2.test("abc", "abc"));



	}
	
	// Function中的R apply(T t)
	// Employee中的String getName();
	@Test
	public void test7() {

		Employee employee= new Employee(1002, "jack", 12, 3232);

		Function<Employee,String> function1 = (t) -> t.getName();

		System.out.println(function1.apply(employee));

		System.out.println("********************************");


		Function<Employee,String> function2 = Employee::getName;
		System.out.println(function2.apply(employee));



	}

}
